import javax.swing.*;
import java.awt.*;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.io.IOException;
import java.nio.file.*;
import java.util.*;
import java.util.List;
import javax.sound.sampled.*;

public class IkunVirusLauncher {

    // 窗口尺寸和展示参数
    private static final int WINDOW_WIDTH = 300;
    private static final int WINDOW_HEIGHT = 300;
    private static final int MAX_WINDOWS = 65;
    private static final double UPDATE_PERCENT = 0.3;
    private static final int DISPLAY_TIME_MS = 200;
    private static final int MARGIN = 10;
    // 资源路径
    private static final String IMAGES_DIR = "/images";
    private static final String BGM_PATH = "/bgm/music.wav";

    public static void main(String[] args) {
        // Windows 风格 LookAndFeel + 中文按钮字体
        try {
            UIManager.setLookAndFeel("com.sun.java.swing.plaf.windows.WindowsLookAndFeel");
            UIManager.put("Button.font", new Font("Microsoft YaHei UI", Font.PLAIN, 16));
        } catch (Exception ignored) {}
        SwingUtilities.invokeLater(IkunVirusLauncher::createAndShowGUI);
    }

    private static void createAndShowGUI() {
        JFrame frame = new JFrame("Ikun 病毒释放器");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JButton launchButton = new JButton("释放IKUN病毒");
        launchButton.setPreferredSize(new Dimension(200, 40));
        launchButton.addActionListener(e -> onLaunchClicked(frame));

        JPanel panel = new JPanel();
        panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
        panel.setBorder(BorderFactory.createEmptyBorder(50, 50, 50, 50));
        panel.add(Box.createVerticalGlue());
        launchButton.setAlignmentX(Component.CENTER_ALIGNMENT);
        panel.add(launchButton);
        panel.add(Box.createVerticalGlue());

        frame.getContentPane().add(panel);
        frame.setSize(400, 200);
        frame.setLocationRelativeTo(null);
        frame.setVisible(true);
    }

    private static void onLaunchClicked(JFrame parent) {
        int result = JOptionPane.showConfirmDialog(
                parent,
                "确认释放IKUN病毒？",
                "⚠️ 危险操作",
                JOptionPane.OK_CANCEL_OPTION,
                JOptionPane.WARNING_MESSAGE
        );
        if (result == JOptionPane.OK_OPTION) {
            playBgm();
            startImageDisplayLoop();
        }
    }

    private static void playBgm() {
        try {
            URL bgmUrl = IkunVirusLauncher.class.getResource(BGM_PATH);
            if (bgmUrl == null) return;
            AudioInputStream ais = AudioSystem.getAudioInputStream(bgmUrl);
            Clip clip = AudioSystem.getClip();
            clip.open(ais);
            clip.loop(Clip.LOOP_CONTINUOUSLY);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private static void startImageDisplayLoop() {
        Thread thread = new Thread(() -> {
            List<String> resourceNames = loadImageResourceNames();
            if (resourceNames.isEmpty()) {
                showError("未找到资源目录: " + IMAGES_DIR);
                return;
            }

            Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
            Random random = new Random();
            List<JWindow> windows = new ArrayList<>();
            int incrementCount = 1;

            while (!Thread.currentThread().isInterrupted()) {
                for (String res : resourceNames) {
                    if (windows.size() < MAX_WINDOWS) {
                        int canAdd = Math.min(incrementCount, MAX_WINDOWS - windows.size());
                        for (int i = 0; i < canAdd; i++) windows.add(createWindow(res, screenSize, random));
                        incrementCount++;
                    } else {
                        int updateCount = Math.max(1, (int) Math.ceil(windows.size() * UPDATE_PERCENT));
                        Set<Integer> idxs = new HashSet<>();
                        while (idxs.size() < updateCount) idxs.add(random.nextInt(windows.size()));
                        for (int idx : idxs) SwingUtilities.invokeLater(() -> updateWindow(windows.get(idx), res, screenSize, random));
                    }
                    try { Thread.sleep(DISPLAY_TIME_MS); } catch (InterruptedException ex) { Thread.currentThread().interrupt(); break; }
                }
            }
            windows.forEach(Window::dispose);
        }, "Image-Display-Thread");
        thread.setDaemon(true);
        thread.start();
    }

    private static List<String> loadImageResourceNames() {
        List<String> names = new ArrayList<>();
        try {
            URL url = IkunVirusLauncher.class.getResource(IMAGES_DIR);
            if (url == null) return names;
            URI uri = url.toURI();
            Path dirPath;
            FileSystem fs = null;
            if ("jar".equals(uri.getScheme())) {
                fs = FileSystems.newFileSystem(uri, Collections.emptyMap());
                dirPath = fs.getPath(IMAGES_DIR);
            } else {
                dirPath = Paths.get(uri);
            }
            try (DirectoryStream<Path> ds = Files.newDirectoryStream(dirPath)) {
                for (Path p : ds) if (Files.isRegularFile(p)) names.add(IMAGES_DIR + "/" + p.getFileName());
            }
            if (fs != null) fs.close();
        } catch (URISyntaxException | IOException e) {
            e.printStackTrace();
        }
        return names;
    }

    private static JWindow createWindow(String resourcePath, Dimension screenSize, Random random) {
        JWindow w = new JWindow();
        updateWindow(w, resourcePath, screenSize, random);
        w.setAlwaysOnTop(true);
        w.setVisible(true);
        return w;
    }

    private static void updateWindow(JWindow w, String resourcePath, Dimension screenSize, Random random) {
        w.getContentPane().removeAll();
        URL imgUrl = IkunVirusLauncher.class.getResource(resourcePath);
        if (imgUrl != null) {
            ImageIcon icon = new ImageIcon(imgUrl);
            Image scaled = icon.getImage().getScaledInstance(WINDOW_WIDTH, WINDOW_HEIGHT, Image.SCALE_SMOOTH);
            w.getContentPane().add(new JLabel(new ImageIcon(scaled)));
            int x = random.nextInt(screenSize.width - WINDOW_WIDTH - MARGIN*2) + MARGIN;
            int y = random.nextInt(screenSize.height - WINDOW_HEIGHT - MARGIN*2) + MARGIN;
            w.setBounds(x, y, WINDOW_WIDTH, WINDOW_HEIGHT);
            w.revalidate(); w.repaint();
        }
    }

    private static void showError(String msg) {
        SwingUtilities.invokeLater(() -> JOptionPane.showMessageDialog(null, msg, "错误", JOptionPane.ERROR_MESSAGE));
    }
}
